home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 7: Sunsite / Linux Cubed Series 7 - Sunsite Vol 1.iso / system / filesyst / dosfs / dmsdosfs.000 / dmsdosfs / dmsdosfs-0.6.9b / ddefrag.c < prev    next >
C/C++ Source or Header  |  1996-06-20  |  4KB  |  177 lines

  1. /* 
  2.  
  3. ddefrag.c
  4.  
  5. DMSDOS filesystem: defragment utility
  6.  
  7. The DMSDOS filesystem was written by Frank Gockel
  8. (gockel@etecs4.uni-duisburg.de).
  9.  
  10. COPYRIGHT (C) 1995,1996 Frank Gockel
  11.  
  12. Distributed under the GNU General Public License.
  13.  
  14. */
  15.  
  16. #include<stdio.h>
  17. #include<linux/dmsdos_fs.h>
  18. #include<sys/ioctl.h>
  19. #include<sys/types.h>
  20. #include<sys/stat.h>
  21. #include<fcntl.h>
  22. #include<string.h>
  23. #include<errno.h>
  24. #include<signal.h>
  25. #include<unistd.h>
  26. #include<stdlib.h>
  27.  
  28. typedef struct
  29. { int clusternr;
  30.   int startsector;
  31. } Clist;
  32.  
  33. Clist clist[65535];
  34.  
  35. int printed;
  36.  
  37. void init_prozent()
  38. { printed=0;
  39.   printf("[0%%                       50%%                     100%%]\n[");
  40. }
  41.  
  42. void prozent(int akt,int end)
  43. { double grmpf;
  44.   int rund;
  45.   int i;
  46.   
  47.   grmpf=53.0*((double)akt)/((double)end);
  48.   rund=grmpf+0.5;
  49.   
  50.   if(rund>printed)
  51.   { for(i=0;i<rund-printed;++i)printf(".");
  52.     printed=rund;
  53.   }  
  54. }
  55.  
  56. void exit_prozent()
  57. { printf("]\n");
  58. }
  59.  
  60. void error(int err)
  61. { if(err==-EPERM)printf("Permission denied.\n");
  62.   else if(err==-EIO)printf("I/O Error.\n");
  63.   else if(err==-EINVAL)printf("Invalid parameter.\n");
  64.   else printf("Error %d occured.\n",err);
  65. }
  66.  
  67. int comparfn(Clist*el1,Clist*el2)
  68. { return el1->startsector-el2->startsector;
  69. }
  70.  
  71. void do_defrag(int fd,int max_cluster)
  72. { int i,ret;
  73.   Mdfat_entry mde;
  74.   unsigned long w[10];
  75.  
  76.   printf("Checking filesystem...\n");
  77.   ioctl(fd,DMSDOS_SIMPLE_CHECK,w);
  78.   if(w[0]==1||w[0]==2)printf("Check aborted due to lack of kernel memory.\n");
  79.   if(w[0]==-1)printf("Filesystem has serious errors: FAT level crosslink(s) found.\n");
  80.   if(w[0]==-2)printf("Filesystem has serious errors: MDFAT level crosslink(s) found.\n");
  81.   if(w[0]==-3)printf("Filesystem has minor errors: BITFAT mismatches MDFAT.\n");
  82.   if(w[0]!=0)
  83.   { printf("Didn't pass filesystem check, program aborted.\n");
  84.     return;
  85.   }             
  86.   
  87.   clist[0].clusternr=0;clist[0].startsector=0;
  88.   clist[1].clusternr=1;clist[1].startsector=0;
  89.   
  90.   printf("Getting info...\n");
  91.   /* get info */
  92.   init_prozent();
  93.   for(i=2;i<=max_cluster;++i)
  94.   { prozent(i-2,max_cluster-2);
  95.     clist[i].clusternr=i;
  96.     w[0]=i;
  97.     w[1]=&mde;
  98.     ret=ioctl(fd,DMSDOS_READ_MDFAT,w);
  99.     if(ret<0){error(ret);return;}
  100.     clist[i].startsector=mde.sector_minus_1+1;
  101.   }
  102.   exit_prozent();
  103.   
  104.   printf("Sorting...\n");
  105.   qsort(&(clist[2]),max_cluster-1,sizeof(Clist),comparfn);
  106.  
  107.   /*
  108.   printf("Sorted list:\n");
  109.   for(i=2;i<max_cluster;++i)
  110.   { printf("Clusternr: %5d          Startsector: %9d\n",
  111.            clist[i].clusternr,clist[i].startsector);
  112.   }
  113.   printf("Not defragmenting.\n");
  114.   return;
  115.   */
  116.   
  117.   printf("Consolidating free space...\n");
  118.   init_prozent();
  119.   for(i=2;i<=max_cluster;++i)
  120.   { prozent(i-2,max_cluster-2);
  121.     ioctl(fd,DMSDOS_MOVEBACK,clist[i].clusternr);
  122.   }
  123.   exit_prozent();
  124.   
  125.   printf("Done.\n");
  126. }
  127.  
  128. void main(int argc, char*argv[])
  129. { Dblsb dblsb;
  130.   int fd;
  131.   int ret;
  132.   
  133.   if(argc!=2)
  134.   {
  135.     printf("DMSDOS defrag utility (C) 1996 Frank Gockel\n");
  136.     printf("Usage: %s (directory)\n",argv[0]);
  137.     return;
  138.   }
  139.   
  140.   fd=open(argv[1],O_RDONLY);
  141.   if(fd<0)
  142.   { printf("No such file or directory.\n");
  143.     return;
  144.   }
  145.   
  146.   /* this hack enables reverse version check */
  147.   dblsb.s_dcluster=DMSDOS_VERSION;
  148.   
  149.   ret=ioctl(fd,DMSDOS_GET_DBLSB,&dblsb);
  150.   if(ret<0)
  151.   { printf("This is not a DMSDOS directory.\n");
  152.     close(fd);
  153.     return;
  154.   }
  155.   printf("You are running DMSDOS Version %d.%d.%d.\n\n",(ret&0xff0000)>>16,
  156.          (ret&0x00ff00)>>8,ret&0xff);
  157.   if(ret&0x0f000000)
  158.   { printf("Sorry, this program is too old for the actual dmsdos version.\n");
  159.     close(fd);
  160.     return;
  161.   }
  162.   if(ret<0x00000608)
  163.   { printf("This program requires at least DMSDOS Version 0.6.8.\n");
  164.     close(fd);
  165.     return;
  166.   }
  167.   if(dblsb.s_comp==READ_ONLY)
  168.   { printf("Sorry, filesystem is mounted read-only.\n");
  169.     close(fd);
  170.     return;
  171.   }
  172.  
  173.   do_defrag(fd,dblsb.s_max_cluster);
  174.   
  175.   close(fd);
  176. }
  177.